#9.1 OldStyle and NewStyle

# class NewStyle(object):
# 	"""docstring for NewStyle"""
# 	def __init__(self, arg):
# 		super(NewStyle, self).__init__()
# 		self.arg = arg
		
# class OldStyle:
# 	def __init__(self, arg):
# 		self.arg = arg
		

# o = OldStyle(11);
# print(o.arg)
# n = NewStyle(22);
# print(n.arg)


#----9.2 ctor  -- init and __init__

# class fooBar():
# 	"""docstring for fooBar"""
# 	def __init__(self, value = 42):
# 		super(fooBar, self).__init__()
# 		self.value = value

# f = fooBar();
# print(f.value)

# b = fooBar("haha ,,i ma not a value");
# print(b.value)

#----9.2.1 rewrite func ,and ctorfunc (init Func)
#----there is something wrong with code follow

# class Bird:
# 	def __init__(self, arg):
# 		self.hungry = arg
# 	def eat(self):
# 		if self.hungry:
# 			print( "Aaaaah...")
# 			self.hungry = False;
# 		else:
# 			print( 'No I am not hungry')


# b = Bird(True);
# b.eat()
# b.eat()

# class SongBird(Bird):
# 	"""docstring for SongBird"""
# 	def __init__(self, arg):
# 		#super(SongBird, self).__init__()
# 		Bird.__init__(self,arg);
# 		self.sound = arg
# 	def sing(self):
# 		print (self.sound)

# sb = SongBird("guaguagua...")
# sb.sing();
# sb.eat();

#----9.3 attr call 
#----9.3 base list and reflect rule


# def checkIndex(key):
# 	if not isinstance(key ,(int)):
# 		raise TypeError
# 	if key < 0:
# 		raise IndexError
# # checkIndex(11);
# # checkIndex("**")
# # checkIndex(-1)

# class ArithmeticSequence():
# 	"""docstring for ArithmeticSequence"""
# 	def __init__(self, start = 0,step = 1):
# 		super(ArithmeticSequence, self).__init__()
# 		self.start = start
# 		self.step = step
# 		self.changed = {}
# 	def __getitem__(self,key):
# 		"""
# 		Get an Item for ArithmeticSequence
# 		"""
# 		checkIndex(key)
# 		try:
# 			return self.changed[key]
# 		except KeyError:
# 			return self.start + key*self.step

# 	def __setitem__(self,key,value):
# 		"""
# 		"change one Item is Sequence"
# 		"""
# 		checkIndex(key)
# 		self.changed[key] = value;

# s = ArithmeticSequence(1,2)
# print(s[4])
# s[4] = 2;
# print(s[4])
# print(s[5])
# print(s[5])
# print(s[100]);
# del s[4];

#----9.3.2 subobjected list&dic&str

# class CounterList(list):		
# 	"""docstring for CounterList"""
# 	def __init__(self, *args):
# 		super(CounterList, self).__init__(*args)
# 		self.counter = 0
# 	def __getitem__(self,index):
# 		self.counter += 1;
# 		return super(CounterList,self).__getitem__(index)


# c1 = CounterList(range(10))
# print(c1)
# print(c1.reverse())
# del c1[3:6]
# print(c1)
# print(c1.counter)
# c1[4] 
# print(c1.counter)
# for x in range(1,10):
# 	c1[4]
# 	print(c1.counter)

#----9.5

# class Rectangle():
# 	"""	property func own  4 param"""
# 	def __init__(self):
# 		super(Rectangle, self).__init__()
# 		self.width = 0
# 		self.height = 0
# 	def setSize(self,size):
# 		self.width ,self.height	= size
# 	def getSize(self):
# 		return	self.width,self.height	
# 	size = property(getSize,setSize)


# r = Rectangle()
# r.width = 10
# r.height= 5
# print(r.size)
# r.size	= 150,100
# print(r.width)


#---- 9.5.2 static and classFunc 	@staticmethod 	@classmethod staticmethod() classmethod()



# __metaclass__ = type

# class MyClass:
# 	"""	"""
# 	def __init__(self):
# 		pass
# 	def smeth():
# 		print("This is a static method")
# 	# smeth = staticmethod(smeth)
# 	def cmeth(cls):
# 		print("This is a class method of",cls)
# 	# cmeth = classmethod(cmeth)

# c = MyClass	()
# MyClass.smeth()
# MyClass.cmeth()
# c.smeth()
# c.cmeth()


# __metaclass__ = type

# class MyClass:
# 	"""	"""
# 	def __init__(self):
# 		pass
# 	@staticmethod
# 	def smeth():
# 		print("This is a static method")
# 	# smeth = staticmethod(smeth)
# 	@classmethod
# 	def cmeth(cls):
# 		print("This is a class method of",cls)
# 	# cmeth = classmethod(cmeth)

# c = MyClass	()
# MyClass.smeth()
# MyClass.cmeth()
# c.smeth()
# c.cmeth()


#---- 9.5.2 __getattr__ __setattr__

# class Rectangle():
# 	"""	"""
# 	def __init__(self):
# 		self.width = 0;
# 		self.height = 0 ;
# 	def __setattr__(self,name,value):
# 		if name == "size":
# 			self.width,self.height	= value	
# 		else:
# 			self.__dict__[name] = value	
# 	def __getattr__(self,name):
# 		if name == "size":
# 			return	self.width,self.height
# 		else:
# 			raise	AttributeError

# r = Rectangle()
# r.size= 100,100
# print(r.size)
# r.count = 1;
# print(r.count)
# print(r.vee)


#---- 9.6 iter && __iter__

#---- 9.6.1 rule of iter

# class 	Fibs():
# 	"""	"""
# 	def __init__(self):
# 		self.a = 0;
# 		self.b = 1;
# 	def __next__(self):
# 		self.a,self.b = self.b,self.a+self.b
# 		return self.a
# 	def __iter__(self):
# 		return	self;
# fibs = Fibs()

# for f in fibs:
# 	if f < 1000000:
# 		print(f)
# 	else:
# 		break



# class Next(object):  
#     def __init__(self, data = 1):  
#         self.data = data  
          
          
#     def __iter__(self):  
#         return self  
      
      
#     def __next__(self):  
#         print("__next__ called")  
#         if self.data > 5:  
#             raise StopIteration  
#         else:  
#             self.data += 1  
#             return self.data  
# for i in Next(3):  
#     print(i) 

#----9.7 generator

nested = [[1,2],[3,4],[5]];

def flatten(nested):
	for sublist in nested:
		for element in sublist:
			yield element

for num in flatten(nested):
	print(num)
	